/*  File Name	: TimerHeap.h
 *  Author		: Javie Pong
 *	 E-mail		: 823960168@qq.com
 *  Created on	: 2012-5-12
 *  Description:
 */

#ifndef TIMERHEAP_H_
#define TIMERHEAP_H_
#include "EventHandler.h"
#include "Lock.h"
#include "ObjectPool.h"

class ReactorImpl;

struct TimerNode
{
	TimerNode(int p=0)
	{
		reset();
	}
	void reset(void);
    bool is_suspend_;
    bool is_pop;
    bool is_cancel;
    bool is_refresh;
    long timer_id_;
    unsigned long next_ticker_; //msec
    unsigned long interval_; //msec
    int heap_index_;
    EventHandler *event_handler_;
};

class TimerHeap
{
public:
	typedef ObjectPool<TimerNode> TimerNodePool;
	typedef std::map<int,TimerNode*> TimerNodeMap;

	TimerHeap(ReactorImpl *reactor);

	virtual ~TimerHeap();

    int open(int max_size);

    long register_timer(EventHandler *eh,TimeValue delay,TimeValue interval);
    int refresh_timer(long timer_id,TimeValue new_time);
    int remove_timer(long timer_id);
    int suspend_timer(long timer_id);
    int resume_timer(long timer_id);

    TimerNode* get_heap_top(void);

    int next_timeout_value(void);
    int timer_count(void);

    int heap_pop(TimerNode *&node);
    int heap_push(TimerNode *node);

    //timer notify fd
    int init_notify_fd(void);
    void close_notify_fd(void);

    int handle_event(void);
public:
    int timer_notify_fd[2];

private:
    void heap_up_sort(int up_node);
    void heap_down_sort(int down_node= 0);
    void heap_earse(TimerNode *node);

    int growth(int size=512);
    long generate_timer_id(void);
    int pool_push(TimerNode *node);

private:
    ReactorImpl *reactor_;
    TimerNode **heap_;

    long timer_id_;
    int max_size_;
    int cur_size_;
    bool is_open_;

    TimerNodeMap node_map_;
    TimerNodePool node_pool_;
    EventHandler handler_;

    RT_MUTEX rt_mutex_;
};


#endif /* TIMERHEAP_H_ */
